<template>
  <div class="wrapper">
    <div class="box">
      <GoBack class="mb24" back-title="企业员工" :title="`${isEdit ? '编辑' : '新建'}员工`" />
      <div>
        <section class="item section-title">基本信息</section>
        <el-form scroll-to-error ref="formRef" :rules="rules" label-position="top" :model="basicInfo" class="row-top">
          <el-form-item prop="avatar">
            <template #label>
              <span>
                头像<span class="card-txt ml10"
                  >若不设置则使用系统默认头像，仅支持JPG、GIF、PNG、BMP格式，且文件不超过3M</span
                >
              </span>
            </template>
            <upload
              :before-upload="beforeUpload"
              accept="image/*"
              :show-file-list="false"
              :on-success="onUpload"
              class="upload-box"
              drag
            >
              <template #trigger>
                <div v-if="!basicInfo.avatar">
                  <el-icon class="el-icon--upload"><upload-filled /></el-icon>
                  <div class="el-upload__text">上传文件</div>
                </div>
                <div class="upload-img" v-else>
                  <img :src="basicInfo.avatar" />
                </div>
              </template>
            </upload>
          </el-form-item>
          <el-row :gutter="20" class="row-top">
            <el-col :span="12">
              <el-form-item prop="jobNum">
                <template #label>
                  <span class="item-title">工号<span class="card-txt ml10">3-6位数字格式</span></span>
                </template>
                <el-input :disabled="isEdit" v-model.trim="basicInfo.jobNum"></el-input>
              </el-form-item>
            </el-col>
            <el-col :span="12">
              <el-form-item prop="name">
                <template #label>
                  <span class="item-title">姓名</span>
                </template>
                <el-input placeholder="请输入" v-model.trim="basicInfo.name" show-word-limit></el-input>
              </el-form-item>
            </el-col>
          </el-row>
          <el-row :gutter="20" class="row-top">
            <el-col :span="12">
              <el-form-item prop="tel">
                <template #label>
                  <span class="item-title"
                    >手机号码<span class="card-txt ml10">呼叫中心中用于手机方式接听和外呼</span></span
                  >
                </template>
                <el-input style="width: 40vw" v-model.trim="basicInfo.tel"></el-input>
              </el-form-item>
            </el-col>
            <el-col :span="12">
              <el-form-item prop="email">
                <template #label>
                  <span class="item-title">邮箱</span>
                </template>
                <el-input
                  style="width: 40vw"
                  placeholder="请输入"
                  v-model.trim="basicInfo.email"
                  show-word-limit
                ></el-input>
              </el-form-item>
            </el-col>
          </el-row>
          <el-row :gutter="20" class="row-top">
            <el-col :span="12">
              <el-form-item prop="crmID">
                <template #label>
                  <span class="item-title">CRM ID<span class="card-txt ml10">用于第三方对接确认员工身份</span></span>
                </template>
                <el-input style="width: 40vw" v-model.trim="basicInfo.crmID"></el-input>
              </el-form-item>
            </el-col>
            <el-col :span="12">
              <el-form-item prop="password">
                <template #label>
                  <span class="item-title">
                    {{ isEdit ? '重置密码' : '初始密码'
                    }}<span class="card-txt ml10">可由字母、数字、特殊符号组成，长度为8-18个字</span>
                  </span>
                </template>
                <el-input
                  style="width: 40vw"
                  placeholder="请输入"
                  v-model="basicInfo.password"
                  show-word-limit
                ></el-input>
              </el-form-item>
            </el-col>
          </el-row>
          <!-- <el-form-item class="item" prop="employeeRole.model">
            <template #label>
              <span class="item-title">员工角色</span>
            </template>
            <el-select-v2
              v-model="basicInfo.employeeRole.model"
              :options="basicInfo.employeeRole.options"
              placeholder="请选择"
              style="width: 40vw"
            />
          </el-form-item> -->
        </el-form>
        <section class="item">
          <p class="item-title">服务组</p>
          <el-transfer
            class="transfer"
            filterable
            :button-texts="['移出服务组', '移入服务组']"
            :titles="['服务组', '已分配组']"
            filter-placeholder="搜索服务组名称"
            v-model="serviceGroup.model"
            :data="serviceGroup.options"
            :props="{ label: 'pathName', key: 'groupNumber' }"
          >
            <template #default="{ option }">
              <el-tooltip :show-after="500" placement="top" :content="`${option.pathName}`">
                <span class="transfer-label">{{ `${option.pathName}` }}</span>
              </el-tooltip>
            </template>
          </el-transfer>
        </section>
      </div>
      <div class="item row-top">
        <section class="item section-title">业务信息</section>
        <section class="item">
          <el-menu mode="horizontal" :default-active="activeIndex">
            <el-menu-item index="0">呼叫中心</el-menu-item>
          </el-menu>
          <div class="call-center-wrapper">
            <div v-if="activeIndex === '0'" class="call-center">
              <div class="card flex-col">
                <div>
                  <p class="card-title">接听方式</p>
                  <p class="card-txt">在客服工作台员工的接听方式，多种方式下员工可自行切换</p>
                </div>
                <div class="dividing"></div>
                <div>
                  <el-checkbox-group class="radio-group" v-model="answeringMethod">
                    <el-checkbox :label="Strategy.ZERO">
                      <span class="login-type">软电话</span>
                      <span class="card-txt">客服工作台的软电话条或者通过软电话SDK集成到其他系统的软件虚拟电话</span>
                    </el-checkbox>
                    <el-checkbox :label="Strategy.ONE">
                      <span class="login-type">手机模式</span>
                      <span class="card-txt">员工绑定的手机号码的手机设备，使用前员工必须绑定手机号码</span>
                    </el-checkbox>
                    <el-checkbox :label="Strategy.TWO">
                      <span class="login-type">SIP话机</span>
                      <span class="card-txt"
                        >每个员工对应使用的一个固定SIP话机，使用前请确定话机已经注册并且绑定员工</span
                      >
                    </el-checkbox>
                  </el-checkbox-group>
                </div>
              </div>
              <div class="card">
                <div>
                  <p class="card-title">整理时长</p>
                  <p class="card-txt">
                    员工结束呼叫后自动进入下一通电话服务的等待状态，处于此状态时不会被分配呼叫，可以进行整理、记录。可设置0-99的整数数字，0为无整理状态。
                  </p>
                </div>
                <input-suffix suffix="秒">
                  <el-input-number
                    :controls="false"
                    v-int
                    v-model="finishingTime"
                    :min="0"
                    :max="99"
                    style="width: 120px"
                    controls-position="right"
                  />
                </input-suffix>
              </div>
              <div class="card flex">
                <div>
                  <p class="card-title">专属外显</p>
                  <p class="card-txt">
                    员工外呼时客户看到号码，未设置专属外显，将从账号内外显号中随机选择。如果在呼叫路由中配置了外显规则，则优先使用外显规则中的外显号码。
                  </p>
                </div>
                <el-select-v2
                  v-model="exAppearance.model"
                  :options="exAppearance.options"
                  placeholder="请选择外显号码"
                  size="large"
                  clearable
                  filterable
                  style="width: 150px"
                  multiple
                />
              </div>
              <div class="card">
                <div>
                  <p class="card-title">SIP号码</p>
                  <p class="card-txt">
                    使用SIP方式呼叫需要员工绑定已注册的SIP话机。除管理员绑定外还可由员工在客服工作台选择空闲SIP自行绑定，或者操作SIP话机拨0000后输入工号进行绑定。
                  </p>
                </div>
                <el-select-v2
                  v-model="SIPNum.model"
                  :options="SIPNum.options"
                  placeholder="请选择SIP号码"
                  filterable
                  clearable
                  size="large"
                  class="select"
                />
              </div>
            </div>
            <JumpMenu wrapperClass="wrapper" boxClass="call-center" titleClass="card-title" />
          </div>
        </section>
      </div>
    </div>
    <div class="btn-box">
      <el-button @click="goBack">取消</el-button>
      <el-button type="primary" @click="onSubmit" class="ml10">确定</el-button>
    </div>
  </div>
</template>
<script setup lang="ts">
import { onMounted, reactive, ref, toRefs } from 'vue'
import { useRouter } from 'vue-router'
import GoBack from '@/common/components/go-back.vue'
import { int as vInt } from '@/app/base/directives/input-int'
import { ServiceGroupState as State, AllocationStrategy as Strategy } from './interface'
import JumpMenu from '../service-group/jump-menu.vue'
import Upload from '@/common/components/upload/index.vue'
import { UploadFilled } from '@element-plus/icons-vue'
import { getQuery, flatten } from '@/common/utils/common'

import { agentCreate, agentUpdate, getServiceGroup, getFullAgent } from '@/app/base/apis/staff'
import md5 from 'js-md5'
import { ExtendFile } from '@/common/utils/upload'
import mcCache from '@/common/utils/mc-get-cache'
import { regexPass, isNumber2 } from '@/common/utils/validate'
import { ElMessage, FormRules } from 'element-plus'
import InputSuffix from '@/common/components/input-suffix.vue'

const state: State = reactive({
  isEdit: false,
  basicInfo: {
    avatar: '',
    jobNum: '',
    name: '',
    tel: '',
    email: '',
    crmID: '',
    password: '',
    employeeRole: {
      model: '',
      options: []
    }
  },
  activeIndex: '0',
  serviceGroup: {
    model: [],
    options: []
  },
  answeringMethod: [Strategy.ZERO, Strategy.ONE, Strategy.TWO],
  finishingTime: 30,
  exAppearance: {
    model: [],
    options: []
  },
  SIPNum: {
    model: '',
    options: []
  }
})
const getFormPass = () => {
  // validator中直接取form值只能取到初始化的"", 所以需要通过方法转换下
  return state.basicInfo.password
}
// 自定义密码的规则验证
const checkPassWord = (rule: any, value: any, callback: any) => {
  if (!state.isEdit && !value) {
    // 不是编辑的时候 && 没有值
    return callback(new Error('请输入密码'))
  } else if (value && !regexPass(value, getFormPass())) {
    callback(
      new Error(
        '密码必须8~18位，并包含数字，小写字母，大写字母，特殊字符中的至少3种，特殊字符不能是%、&、+、\'、\\"、<、>、='
      )
    )
  } else {
    callback()
  }
}
// 自定义工号的规则验证
const checkJobNum = (rule: any, value: any, callback: any) => {
  if (!value) {
    return callback(new Error('请输入工号'))
  } else {
    if (value && (!isNumber2(value) || value.length < 3 || value.length > 6)) {
      callback(new Error('请输入3-6位数字'))
    } else {
      callback()
    }
  }
}
// 手机号格式
const checkTel = (rule: any, value: any, callback: any) => {
  if (value && !isNumber2(value)) {
    callback(new Error('请输入正确的手机号'))
  } else {
    callback()
  }
}
const rules = reactive<FormRules>({
  jobNum: [{ validator: checkJobNum, required: true, trigger: 'blur' }],
  name: [{ required: true, message: '姓名必填', trigger: 'blur' }],
  password: [{ validator: checkPassWord, required: true, trigger: 'blur' }],
  'employeeRole.model': [{ required: true, message: '员工角色必选', trigger: 'change' }],
  tel: [{ trigger: 'blur', validator: checkTel }],
  email: [
    {
      message: '邮箱格式不正确',
      trigger: 'blur',
      pattern: /^[a-zA-Z0-9]+([-_.][A-Za-zd]+)*@([a-zA-Z0-9]+[-.])+[A-Za-zd]{2,5}$/
    }
  ]
})
const { isEdit, basicInfo, activeIndex, serviceGroup, answeringMethod, finishingTime, exAppearance, SIPNum } =
  toRefs(state)

const formRef = ref(null)
const router = useRouter()

onMounted(async () => {
  await mcCache.$getCache('userCache', 'hasObj')
  getLocalData()
  getAllServiceGroup()
  mcCache.$getCache('explicNum').then((data: any) => {
    // 获取外显号列表
    state.exAppearance.options = handleNumList(data || [], 'id')
  })
  mcCache.$getCache('sipNum').then((data: any) => {
    // 获取sip号列表
    state.SIPNum.options = handleNumList(data || [], 'id')
  })
})
// 处理缓存的列表数据
const handleNumList = (list: any, type: string) => {
  return list.map((item: any) => {
    return { label: item[type], value: item[type] }
  })
}

const getLocalData = async () => {
  const query = getQuery()
  state.isEdit = !!query.id
  if (query.id) {
    const res: any = await getFullAgent({
      agentId: query.id
    })
    const data: any = res.data
    const { groups } = data
    const { basicInfo: info, answeringMethod, finishingTime, exAppearance, SIPNum } = transOrigin(data)
    Object.assign(state.basicInfo, info)
    state.answeringMethod = answeringMethod
    state.finishingTime = finishingTime
    state.exAppearance.model = exAppearance
    state.SIPNum.model = SIPNum
    state.serviceGroup.model = groups
  }
}

const getAllServiceGroup = async () => {
  const res = await getServiceGroup()
  state.serviceGroup.options = flatten(res.data)
}

const goBack = () => {
  router.back()
}

const onUpload = (file: ExtendFile) => {
  state.basicInfo.avatar = file.url || ''
}

const beforeUpload = async (file: ExtendFile) => {
  if (file.size > 1024 * 1024 * 3) {
    ElMessage.error('上传大小不超过3M')
    return false
  }
  return true
}

const transOrigin = (data: any) => {
  const { icon, agentNumber, agentName, mobile, email, crmId, password } = data
  const { loginType, restTime, numbers, sipNumber } = data.agentCallConfig || {}
  return {
    basicInfo: {
      avatar: icon,
      jobNum: agentNumber,
      name: agentName,
      tel: mobile,
      email: email,
      crmID: crmId,
      password: password
    },
    answeringMethod: loginType,
    finishingTime: restTime,
    exAppearance: numbers || [],
    SIPNum: sipNumber || ''
  }
}

const transform = () => {
  return {
    agentCallConfig: {
      loginType: state.answeringMethod,
      numbers: state.exAppearance.model,
      restTime: state.finishingTime,
      sipNumber: state.SIPNum.model
    },
    agentName: state.basicInfo.name,
    agentNumber: state.basicInfo.jobNum,
    crmId: state.basicInfo.crmID,
    email: state.basicInfo.email,
    icon: state.basicInfo.avatar,
    mobile: state.basicInfo.tel,
    password: state.basicInfo.password ? md5(state.basicInfo.password) : state.basicInfo.password, // 没有值的情况下md5会报错
    groups: state.serviceGroup.model
  }
}

const onSubmit = async () => {
  if (!formRef.value) {
    return
  }
  await (formRef.value as any).validate(async (valid: any, fields: any) => {
    if (valid) {
      const isCreate = !state.isEdit
      const data = transform()
      const id = getQuery().id
      const res = await (isCreate ? agentCreate : agentUpdate)({
        ...(isCreate ? {} : { _id: id }),
        ...data
      })
      if (isCreate) {
        mcCache.$addOneCache('userCache', res.data, 'hasObj', '_id')
      } else {
        mcCache.$updateCache('userCache', res.data, '_id', 'hasObj')
      }
      router.back()
    } else {
      console.log('error submit!', fields)
    }
  })
}
</script>
<style lang="stylus" scoped>
.wrapper
  height: 90vh;
  overflow-y: scroll;
  :deep(.el-form-item)
   margin-bottom 0
.require::before
  content '*'
  font-size 10px
  color var(--el-color-success)
  position relative
  top: 0px;
  right: 2px;

.select
  :deep(.el-tooltip__trigger)
    width: 150px;
.no-child-margin
  p
   margin 0
   color rgba(0, 0, 0, 0.6)
.radio-group
  display flex
  flex-direction: column;
  align-items: unset;
  .login-type
    display inline-block
    min-width 60px
    padding-right 12px
.no-justify
  justify-content unset !important

.primary-color
  color var(--el-color-primary-dark)
.noMargin
  margin 0 !important
.box
  padding 10px 24px 24px
  margin-bottom: 50px;
  border-bottom 1px solid var(--el-disabled-border-color)
.call-center-wrapper
  display flex
  margin-top 20px
.mt27
  margin-top: 27px;
.transfer
  :deep(.el-transfer-panel .el-transfer-panel__header)
      background: linear-gradient(0deg, rgba(30, 99, 245, 0.1), rgba(30, 99, 245, 0.1)), #FFFFFF;
  :deep(.el-transfer-panel__filter .el-input__wrapper)
    border-radius: 18px;
  :deep(.el-transfer-panel .el-checkbox__label)
    font-size 14px

.flex-col
.item
  margin-top 16px
  :deep(.el-transfer__button:nth-child(1))
    display block
  :deep(.el-transfer__button:nth-child(2))
   margin-top 20px
   margin-left 0
  :deep(.el-menu-item)
   height: 40px;
   padding: 20px 0;
  :deep(.el-transfer-panel__filter .el-input__inner)
    padding-left 2px
.section-title
  height: 36px;
  display: flex;
  box-sizing: border-box;
  align-items: center;
  padding: 8px 16px;
  border-radius: 4px;
  font-weight: 500;
  font-size: 14px;
  color: var(--el-overlay-color);
  background: linear-gradient(0deg, rgba(30, 99, 245, 0.1), rgba(30, 99, 245, 0.1)), #FFFFFF;
.row-top
  padding-top 16px

.card-txt
  font-size 12px
  color rgba(0, 0, 0, 0.6)
  margin-right 20px
  line-height: 24px;
  margin-bottom: 0;
  margin-top: 8px;

.flex
 display flex
 justify-content space-between
 align-items center
.card
  border 1px solid var(--el-disabled-border-color)
  border-radius 4px
  padding: 16px;
  margin-bottom 20px
  display: flex;
  align-items: center;
  justify-content: space-between;
.flex-col
  flex-direction column
  align-items unset
.dividing
  width 100%
  height 1px
  background var(--el-disabled-border-color)
  margin: 11px 0;
.card-title
  margin: 0;
.card-title, .item-title
  font-weight 500
  color: var(--el-overlay-color)
.card-text
  color var(--el-mask-color-extra-light)
.btn-box
  height: 60px;
  line-height: 60px;
  text-align: right;
  padding: 0 14px;
  position: fixed;
  bottom: 0;
  right: 0;
  left: 265px;
  padding-right: 30px;
.ml10
  margin-left 10px
.mt16
  margin-top 16px
.fs20
  font-size 20px
.tip-icon
  color rgba(0, 0, 0, 0.38)
.upload-box
  :deep(.el-upload-dragger)
    height: 120px;
    width 120px
    display: flex;
    justify-content center
    align-items: center;
    // padding: 10px;
  :deep(.el-icon--upload)
    font-size: 20px;
    margin-bottom: 0px;
  // .el-icon-upload
  //   line-height 24px
  // .el-upload,.el-upload-dragger
  //   width 100%
  // .el-upload-dragger .el-upload__text em
  //   color $c-main
  // .el-upload__text
  //   margin-top -14px
.upload-img
  width 100%
  img
    width 100%
  .file-limit
    font-size 12px
.mb24
  margin-bottom 24px
</style>
